package com.yplan.dm;

import com.google.protobuf.InvalidProtocolBufferException;
import com.microsoft.playwright.*;
import com.yplan.dm.bilibili.danmaku.message.DankamuService;
import com.yplan.dm.bilibili.utils.Utils;
//import com.yplan.dm.proto.DANMUVO;
import com.yplan.dm.proto.DanmuvoWSS;
import com.yplan.dm.proto.WSS;
import io.grpc.testing.TestUtils;
import io.netty.util.internal.StringUtil;

import java.io.*;
import java.net.URLDecoder;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.function.Consumer;


public class DanmuHelper {
    Thread thread;
    boolean isRunning = false;
    SocketClientManager manager;
    boolean stop = false;
    public String ip;
    public String url;
    public int port = 80;
    public danmu danmu;
    public int type = 0;

    public DanmuHelper(String ip, int port, danmu danmu) {
        this.danmu = danmu;
        this.ip = ip;
        this.port = port;
    }

    public void setInfo(String ip, int port, String url, int type) {
        this.ip = ip;
        this.port = port;
        this.url = url;
        this.type = type;
    }

    public void start() {
        if (StringUtil.isNullOrEmpty(ip)) return;
        if (isRunning) {
            stop = true;
            if (danmu != null)
                danmu.textArea1.append("上次链接未关闭，请稍后重试\n");
        } else {
            if (thread != null) thread.interrupt();
            thread = new Thread(runnable);
            thread.start();
            danmu.textArea1.setText("");
            danmu.textArea1.append("开始抓取弹幕|房间地址【" + url + "】|游戏服务地址：【" + ip + ":" + port + "】\n");

        }

    }

    public void stop() {
        danmu.textArea1.append("正在停止弹幕抓取...\n");
        stop = true;
        if (dankamuService != null) {
            dankamuService.close();
            closeManager();
        }
    }

    Runnable runnable = new Runnable() {
        @Override
        public void run() {
            isRunning = true;
            stop = false;
            manager = new SocketClientManager(ip, port, danmu != null ? danmu.textArea1 : null);
            danmu.lButton.setEnabled(false);
            danmu.rButton.setEnabled(true);
            danmu.textArea1.append("explorer准备中---------------第一次使用弹幕助手等待时间较长，请耐心等候" + "\n");

//            switch (type) {
//                case 0:
            trackDouyin();
//                    break;
//                case 1:
//                    trackBilibili();
//            }
        }
    };
    DankamuService dankamuService;

    private void trackBilibili() {
        try {
            dankamuService = new DankamuService(url);
            dankamuService.start();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    private void trackDouyin() {
        try (Playwright playwright = Playwright.create()) {
            Browser browser = playwright.webkit().launch();
            Page page = browser.newPage();
//                page.emulateMedia(null);
            System.out.println("正在访问抖音直播间"+url+"\n"+ "-------------------请稍后" + "\n");
//            danmu.textArea1.append("正在访问抖音直播间------------------------------请稍后" + "\n");
            Map<String, String> map = new HashMap<>();
            Consumer<Request> listener = request -> {
//                    if (request.url().startsWith("https://live.douyin.com/webcast/im/fetch/?")) {
            };
            //监听websocket
            page.onWebSocket(new Consumer<WebSocket>() {
                @Override
                public void accept(WebSocket webSocket) {
                    webSocket.onFrameReceived(new Consumer<WebSocketFrame>() {
                        @Override
                        public void accept(WebSocketFrame webSocketFrame) {
                            final byte[] data = webSocketFrame.binary();
                            System.out.println("：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：::");
                            try {
                                //最外层解析 try catch 不指定ws路径也可以，解析失败不会崩溃
                                //proto解析外层
                                WSS.WssResponse wss = WSS.WssResponse.parseFrom(data);
//                                System.out.println(wss);
                                //GZIP解压data数据
                                final byte[] uncompress = Utils.uncompress(wss.getData());
                                //解析data
                                DanmuvoWSS.Response response = DanmuvoWSS.Response.parseFrom(uncompress);
                                final List<DanmuvoWSS.Message> messagesList = response.getMessagesList();
//                                System.out.println(messagesList);
                                //根据message区分message类型解析 与之前接口相同
                                decodeMessage(messagesList);
                            } catch (InvalidProtocolBufferException e) {
                                e.printStackTrace();
                            }

                            System.out.println("11111111111111111111111111111111111111111111111111111111111111111111111111111111");
                            System.out.println("：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：：::");

                        }
                    });
                }
            });

            page.onRequestFinished(listener);
//                page.navigate("https://live.douyin.com/720911644621");
            //访问页面
            page.navigate(url);
//                browser.startTracing();

            while (true) {
                try {
                    //循环访问激活页面
                    page.content();
                    if (stop) {
                        if (manager != null) {
                            browser.close();
                            closeManager();

                        }
                        break;
                    }
                    Thread.sleep(10000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }

        }
    }
    private void decodeMessage(List<DanmuvoWSS.Message> messagesList) {
        if (messagesList == null) return;
        messagesList.forEach(item -> {
            if ("WebcastMemberMessage".equals(item.getMethod())) {

                return;
            }

            if ("WebcastSocialMessage".equals(item.getMethod())) {

                return;
            }

            if ("WebcastChatMessage".equals(item.getMethod())) {
                try {
                    DanmuvoWSS.ChatMessage chatMessage = DanmuvoWSS.ChatMessage.parseFrom(item.getPayload());
                    System.out.println("[弹幕消息]" + chatMessage.getUser().getNickname() + "(" + chatMessage.getUser().getId() + ")" + "说：" + chatMessage.getContent() + "\n");
                    danmu.textArea1.append("[弹幕消息]" + chatMessage.getUser().getNickname() + "(" + chatMessage.getUser().getId() + ")" + "说：" + chatMessage.getContent() + "\n");
//                    manager.send("msg\0" + chatMessage.getUser().getId() + "\0" + chatMessage.getUser().getNickname() + "\0" + chatMessage.getContent()
//                            + "\0" + chatMessage.getUser().getAvatarThumb().getUri() + "\0", danmu.textArea1);
                } catch (InvalidProtocolBufferException e) {
                    e.printStackTrace();
                }
                return;
            }


            if ("WebcastLikeMessage".equals(item.getMethod())) {

                return;
            }

            if ("WebcastGiftMessage".equals(item.getMethod())) {

                return;
            }

            if ("WebcastRoomUserSeqMessage".equals(item.getMethod())) {

                return;
            }


        });


    }
//     try {
//        if (request.url().startsWith("ws")) {
//            log(String.valueOf(map) + "------------------------------=========-----------------------");
//            log(String.valueOf(map) + "---------------begin---------------=========-----------------------");
//
//        }
//
//    } catch (Exception e) {
//        e.printStackTrace();
//    }
//    //                    page.content();
    //                        DanmuvoWSS.DYDM chatMessage = DANMUVO.DYDM.parseFrom(request.response().body());
//                        chatMessage.getMessagesList().forEach(item -> {
//                            if ("WebcastChatMessage".equals(item.getMethod())) {
//                                try {
//                        final DANMUVO.ChatMessage chatMessage1 = DANMUVO.ChatMessage.parseFrom(item.getPayload());
//                        danmu.textArea1.append("[弹幕消息]" + chatMessage1.getUser().getNickname() + "(" + chatMessage1.getUser().getId() + ")" + "说：" + chatMessage1.getContent() + "\n");
//                        manager.send("msg\0" + chatMessage1.getUser().getId() + "\0" + chatMessage1.getUser().getNickname() + "\0" + chatMessage1.getContent()
//                                + "\0" + chatMessage1.getUser().getAvatarThumb().getImgUrl() + "\0", danmu.textArea1);
//                                } catch (InvalidProtocolBufferException e) {
//                                    e.printStackTrace();
//                                }
//                            }
//                            map.put(item.getMethod(), item.getMethod());
//                            if ("WebcastGiftMessage".equals(item.getMethod())) {
//                                try {
//                                    final DANMUVO.GiftMessage giftMessage = DANMUVO.GiftMessage.parseFrom(item.getPayload());
////                                    log("--------------------------------------------------------------");
////                                    log(String.valueOf(giftMessage.getGift().getName()));
////                                    log("------------------------------=========-----------------------");
//                                    danmu.textArea1.append("[礼物消息]" + giftMessage.getUser().getNickname() + "(" + giftMessage.getUser().getId() + ")" + "赠送礼物：【" + giftMessage.getGift().getName() + "】\n");
//                                    manager.send("gift\0" + giftMessage.getUser().getId() + "\0" + giftMessage.getUser().getNickname() + "\0" + giftMessage.getGift().getName()
//                                            + "\0" + giftMessage.getUser().getAvatarThumb().getImgUrl() + "\0", danmu.textArea1);
//                                } catch (InvalidProtocolBufferException e) {
//                                    e.printStackTrace();
//                                }
//                            }
//                        });


    private void closeManager() {
        manager.close();
        isRunning = false;
        danmu.lButton.setEnabled(true);
        danmu.rButton.setEnabled(false);
        stop = false;
        danmu.textArea1.append("已停止...\n");

    }


    public static void log(String log) {
        System.out.println(log + "\n");
    }

    public static void outPutToFile(String name, byte[] bytes) {
        if (bytes != null) {
            Path path = Paths.get(name + ".txt");
            File file = new File(path.toString());
            if (file.exists()) file.delete();
            try {
                file.createNewFile();
                FileOutputStream fp = new FileOutputStream(file);
                fp.write(bytes);
                fp.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    private static Map getParamsMap(String queryString, String enc) {
        Map paramsMap = new HashMap();
        if (queryString != null && queryString.length() > 0) {
            int ampersandIndex, lastAmpersandIndex = 0;
            String subStr, param, value;
            String[] paramPair, values, newValues;
            do {
                ampersandIndex = queryString.indexOf('&', lastAmpersandIndex) + 1;
                if (ampersandIndex > 0) {
                    subStr = queryString.substring(lastAmpersandIndex, ampersandIndex - 1);
                    lastAmpersandIndex = ampersandIndex;
                } else {
                    subStr = queryString.substring(lastAmpersandIndex);
                }
                paramPair = subStr.split("=");
                param = paramPair[0];
                value = paramPair.length == 1 ? "" : paramPair[1];
                try {
                    value = URLDecoder.decode(value, enc);
                } catch (UnsupportedEncodingException ignored) {
                }
                if (paramsMap.containsKey(param)) {
                    values = (String[]) paramsMap.get(param);
                    int len = values.length;
                    newValues = new String[len + 1];
                    System.arraycopy(values, 0, newValues, 0, len);
                    newValues[len] = value;
                } else {
                    newValues = new String[]{value};
                }
                paramsMap.put(param, newValues);
            } while (ampersandIndex > 0);
        }
        return paramsMap;
    }


//            page.onWebSocket(ws -> {
//                log("WebSocket opened: " + ws.url());
//                ws.onFrameSent(frameData -> log(frameData.text()));
//                ws.onFrameReceived(frameData -> log(frameData.text()));
//                ws.onClose(ws1 -> log("WebSocket closed"));
//            });

//            page.onRequest(request -> System.out.println("Request sent: " + request.url()));
}
